package com.safety.hat.service.impl.hat;

import com.alibaba.fastjson.JSONObject;
import com.safety.hat.data.ACTEnum;
import com.safety.hat.data.Result;
import com.safety.hat.data.hat.HatLoginBO;
import com.safety.hat.service.hat.adapter.IHatSocketUserAdapterService;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Service;

import javax.websocket.Session;
import java.util.Objects;
import java.util.Optional;
import java.util.concurrent.ConcurrentHashMap;

/**
 * @Author: lijun
 * @Date: 2020/5/24 下午10:31
 */
@Service
@Slf4j
public class HatSocketUserAdapterServiceImpl implements IHatSocketUserAdapterService<HatLoginBO> {

    /**
     * 记录登录设备
     */
    private static final ConcurrentHashMap<String, Session> loginDevice = new ConcurrentHashMap<>(64);

    /**
     * 获取所有的 device, key：deviceId
     */
    @Override
    public ConcurrentHashMap<String, Session> getAllOnLineHatUser() {
        return new ConcurrentHashMap<>(loginDevice);
    }

    /**
     * 删除信息
     */
    @Override
    public void removeInfo(String deviceId) {
        if (StringUtils.isNoneBlank(deviceId)) {
            loginDevice.remove(deviceId);
        }
    }

    /**
     * 删除信息
     */
    @Override
    public void removeInfo(Session session) {
        Optional<String> removeKey = loginDevice.entrySet().stream()
                .filter(entry -> entry.getValue().equals(session))
                .map(entry -> entry.getKey())
                .findAny();
        log.info("删除缓存连接：sessionId = {},removeKey = {}", session.getId(), removeKey);
        if (removeKey.isPresent() && StringUtils.isNoneBlank(removeKey.get())) {
            loginDevice.remove(removeKey.get());
        }
    }

    /**
     * 新增一个 session 用以处理断线重连情况
     */
    @Override
    @Async
    public void asyncCheckAndPutSession(String deviceId, Session session) {
        if (StringUtils.isNoneBlank(deviceId) && Objects.nonNull(session)) {
            loginDevice.putIfAbsent(deviceId, session);
        }
    }


    /**
     * 处理消息
     */
    @Override
    public void handleMessage(HatLoginBO message, Session session) {
        loginDevice.put(message.getDeviceId(), session);
        System.out.println("设备登录 ：" + message.getDeviceId());
        session.getAsyncRemote().sendText(JSONObject.toJSONString(Result.defaultResult(ACTEnum.HAT_LOGIN)));
    }

    /**
     * 获取设备ID
     */
    @Override
    public String getDeviceId(String message) {
        return transMessageToObject(message).getDeviceId();
    }

    /**
     * 根据当前行为判断是否可以被处理
     */
    @Override
    public boolean canHandle(String act) {
        return ACTEnum.HAT_LOGIN.is(act);
    }

    @Override
    public Class<HatLoginBO> getMessageClass() {
        return HatLoginBO.class;
    }

}
